﻿using System;
using System.Collections.Generic;
using System.Text;
using Young3.FMSearch.Core.Entities.GameVersions;
using Young3.FMSearch.Core.Managers;
using Young3.FMSearch.Core.Offsets;
using Young3.FMSearch.Core.Attributes;

namespace Young3.FMSearch.Core.Entities.InGame
{
    public class Club : BaseObject
    {
        public Club(int memoryAddress, IVersion version)
            : base(memoryAddress, version)
        { }
        
        public Club(int memoryAddress, ArraySegment<byte> originalBytes, IVersion version)
            : base(memoryAddress, originalBytes, version)
        { }

        [FMPointer(ClubOffsets.Chairman)]
        public Staff Chairman { get; internal set; }

        [FMEntityAttribute(ClubOffsets.Name)]
        public string Name { get; internal set; }

        [FMEntityAttribute(ClubOffsets.ShortName)]
        public string ShortName { get; internal set; }

        [FMEntityAttribute(ClubOffsets.NickName)]
        public string NickName { get; internal set; }

        [FMEntity(ClubOffsets.ID)]
        public Int32 ID { get; private set; }

        [FMEntityAttribute(ClubOffsets.Morale)]
        public Int16 Morale { get; set; }

        [FMEntityAttribute(ClubOffsets.YearFounded)]
        public Int16 YearFounded { get; set; }

        [FMEntityAttribute(ClubOffsets.NumberOfAffiliatedClubs)]
        public byte NumberOfAffiliatedClubs { get; set; }

        [FMEntityAttribute(ClubOffsets.MaxAffiliatedClubNumber)]
        public byte MaxAffiliatedClubNumber { get; set; }

        //[FMEntityAttribute(ClubOffsets.number)]
        //public Int32 SeasonTicketHolders { get; set; }

        [FMEntityAttribute(ClubOffsets.AverageAttendance)]
        public Int32 AverageAttendance { get; set; }

        [FMEntityAttribute(ClubOffsets.TeamNumber)]
        public byte TeamNumber { get; set; }

        //[FMEntityAttribute(ClubOffsets.numb)]
        //public Int16 ClubsNumber { get; set; }

        [FMEntityAttribute(ClubOffsets.DirectorNumber)]
        public Int16 DirectorNumber { get; set; }

        [FMEntityAttribute(ClubOffsets.ScoutNumber)]
        public Int16 ScoutNumber { get; set; }

        //[FMEntityAttribute(ClubOffsets.ScoutAddress)]
        //public Int32 ScoutAddress { get; set; }

        [FMEntityAttribute(ClubOffsets.FinanceAddress)]
        internal Int32 FinanceAddress { get; set; }

        //[FMEntityAttribute(ClubOffsets.Country)]
        //public Int32 CountryAddress { get; set; }

        [FMEntityAttribute(ClubOffsets.MaximumAttendance)]
        public Int32 MaximumAttendance { get; set; }

        [FMEntityAttribute(ClubOffsets.MinimumAttendance)]
        public Int32 MinimumAttendance { get; set; }

        [FMEntityAttribute(ClubOffsets.TrainingGround)]
        public byte TrainingFacilities { get; set; }

        [FMEntityAttribute(ClubOffsets.YouthSetup)]
        public byte YouthFacilities { get; set; }

        [FMEntityAttribute(ClubOffsets.YouthAcademy)]
        public byte YouthAcademy { get; set; }

        [FMEntityAttribute(ClubOffsets.TeamAddress)]
        public Int32 TeamAddress { get; set; }

        [FMEntityAttribute(ClubOffsets.DirectorAddress)]
        public Int32 DirectorAddress { get; set; }

        [FMPointer(ClubOffsets.Country)]
        public Country Country { get; internal set; }

        [FMPointer(ClubOffsets.FinanceAddress)]
        public Finance Finances { get; internal set; }

        [FMEntity(ClubOffsets.Status)]
        public byte Status {get;set;}
        public ClubStatus ClubStatus
        {
            get { return (ClubStatus)Status; }
            set { Status = (Byte)value; }
        }

        public List<Team> Teams
        {
            get
            {
                List<Team> ret = new List<Team>();
                for (int i = 0; i < TeamNumber; i++)
                {
                    var memAddr = ProcessManager.ReadInt32(TeamAddress + (i * 0x4));
                    ret.Add(((Dictionary<int,Team>)ObjectManagerWrapper.ObjectManagers[DatabaseMode].ObjectStore[typeof(Team)])[memAddr]);
                }
                return ret;
            }
        }

        //public List<Staff> Scouts
        //{
        //    get
        //    {
        //        List<Staff> ret = new List<Staff>();
        //        for (int i = 0; i < ScoutNumber; i++)
        //            ret.Add(new Staff(ProcessManager.ReadInt32(ScoutAddress + (i * 0x4))));
        //        return ret;
        //    }
        //}

        public List<Staff> Directors
        {
            get
            {
                List<Staff> ret = new List<Staff>();
                for (int i = 0; i < DirectorNumber; i++)
                    ret.Add(new Staff(ProcessManager.ReadInt32(DirectorAddress + (i * 0x4)), Version));
                return ret;
            }
        }

        public override string ToString()
        {
            return Name;
        }

        //TODO: Implement Kit

        //TODO: Implement Sponsor
    }

    public enum ClubStatus
    {
        Professional = 1,
        SemiProfessional = 2,
        Amateur = 3
    }
}